package com.huiquan.foundation.dao;

import java.util.HashMap;
import java.util.List;
import java.util.Map;

import javax.annotation.Resource;

import org.apache.commons.lang.StringUtils;
import org.springframework.stereotype.Repository;

import com.huiquan.foundation.domain.Subpackage;
import com.huiquan.framework.base.EnhancedBaseDao;
import com.ibatis.sqlmap.client.SqlMapClient;

/**
 * @author lichao email:lichao@witspring.com
 * @Description: 分包dao
 * @Date 2017/11/21 11:02
 * @since Ver V
 */
@Repository
public class SubpackageDao extends EnhancedBaseDao<Subpackage> {

    @Resource(name = "sqlMapClient")
    private SqlMapClient sqlMapClient;

    public static final String space = "SUBPACKAGE.";

    public SubpackageDao() {
        super(space);
    }

    /**
     * 清空指定类型的数据
     *
     * @param type
     * @param level
     */
    public void deleteDataWithType(Integer type, Integer level) {
        Map<String, Object> params = new HashMap<>();
        params.put("type", type);
        params.put("level", level);
        this.delete(space + "DELETE_DATA_WITH_TYPE", params, sqlMapClient);
    }

    /**
     * 初始化分包表并批量插入数据
     *
     * @param type
     * @param level
     * @param idPackageList
     * @param param
     */
    public void batchInsertForInit(Integer type, Integer level, List<String> idPackageList, String param) {
        Map<String, Object> params = new HashMap<>();
        params.put("type", type);
        params.put("level", level);
        params.put("param", param);

        int start = 0, end, size = idPackageList.size();
        List<String> tempList;

        while (start < size) {
            if (start + 2000 < size) {
                end = start + 2000;
            } else {
                end = size;
            }
            tempList = idPackageList.subList(start, end);
            params.put("idPackageList", tempList);
            this.insert(space + "INSERT_BATCH_FOR_INIT", params, sqlMapClient);
            // 将关联的sentence语句置为已分包但未分配状态（label_status=3)
            for (String idPackageStr : idPackageList) {
                this.update(space + "UPDATE_SENTENCE_LABEL_STATUS_TO_SUBPACKAGED", idPackageStr, sqlMapClient);
            }
            start += 2000;
        }
    }


    /**
     * 检索未分配包数据
     *
     * @param type
     * @param level
     * @param param
     * @return
     */
    public Subpackage selectUndistributedData(int type, String level, String param) {
        Map<String, Object> params = new HashMap<>();
        params.put("type", type);
        if (StringUtils.isNotEmpty(level)) {
            params.put("level", level);
        }
        if (StringUtils.isNotEmpty(param)) {
            params.put("param", param);
        }
        return (Subpackage) this.object(space + "SELECT_UNDISTRIBUTED_DATA", params, sqlMapClient);
    }

    /**
     * 更新包的uid
     *
     * @param id
     * @param uid
     */
    public void updateUidWithId(long id, long uid) {
        Map<String, Object> params = new HashMap<>();
        params.put("id", id);
        params.put("uid", uid);
        this.update(space + "UPDATE_UID_WITH_ID", params, sqlMapClient);
    }

    /**
     * 检索分包出的数据中已标记的数据的id列表（弃用）
     *
     * @param type
     * @param secondType
     * @return
     */
//    public List<Long> selectOutsourcingSentenceLabeledIdList(int type, String secondType) {
//        Map<String, Object> params = new HashMap<>();
//        params.put("type", type);
//        params.put("secondType", secondType);
//        return (List<Long>) this.list(space + "SELECT_OUTSOURCING_SENTENCE_LABELED_ID_LIST", params, sqlMapClient);
//    }

    /**
     * 检索未标记的数据的id列表
     *
     * @param type
     * @param secondType
     * @param lengthLowerLimit 词语长度下限
     * @param lengthUpperLimit 词语长度上限
     * @return
     */
    public List<Long> selectSentenceUnlabelIdList(int type, String secondType, Integer lengthLowerLimit, Integer lengthUpperLimit) {
        Map<String, Object> params = new HashMap<>();
        params.put("type", type);
        params.put("secondType", secondType);
        params.put("lengthLowerLimit", lengthLowerLimit);
        params.put("lengthUpperLimit", lengthUpperLimit);
        return (List<Long>) this.list(space + "SELECT_SENTENCE_UNLABEL_ID_LIST", params, sqlMapClient);
    }

    /**
     * 获取数据总数
     *
     * @param secondType
     * @return
     */
    public Integer getDataCount(String secondType) {
        Map<String, Object> params = new HashMap<>();
        params.put("secondType", secondType);
        return (Integer) this.object(space + "SELECT_DATA_COUNT", params, sqlMapClient);
    }

    /**
     * 获取用户关联等级的数据的count
     *
     * @param secondType
     * @param uid
     * @param level
     * @param levelSize
     * @return
     */
    public Integer getLevelDataCountWithUid(String secondType, long uid, int level, int levelSize) {
        Map<String, Object> params = new HashMap<>();
        params.put("secondType", secondType);
        params.put("uid", uid);
        params.put("startIndex", level * levelSize);
        params.put("size", levelSize);
        return (Integer) this.object(space + "SELECT_LEVEL_DATA_COUNT_WITH_UID", params, sqlMapClient);
    }

    /**
     * 获取用户关联等级的数据
     *
     * @param secondType
     * @param uid
     * @param level
     * @param levelSize
     * @return
     */
    public List<Long> getLevelDataWithUid(String secondType, long uid, int level, int levelSize) {
        Map<String, Object> params = new HashMap<>();
        params.put("secondType", secondType);
        params.put("uid", uid);
        params.put("startIndex", level * levelSize);
        params.put("size", levelSize);
        return (List<Long>) this.list(space + "SELECT_LEVEL_DATA_WITH_UID", params, sqlMapClient);
    }

    /**
     * 把sid和uid关系写入到t_sentence_user_relation表
     *
     * @param uid
     * @param sidList
     */
    public void insertSentenceUserRelation(long uid, List<Long> sidList) {
        Map<String, Object> params = new HashMap<>();
        params.put("uid", uid);
        params.put("sidList", sidList);
        this.insert(space + "INSERT_SENTENCE_USER_RELATION", params, sqlMapClient);
    }

    /**
     * 把指定id的sentence数据的状态置为半标注
     *
     * @param sidListStr
     */
    public void updateSentenceStatusToHalfLabeled(String sidListStr) {
        Map<String, Object> params = new HashMap<>();
        params.put("sidListStr", sidListStr);
        this.update(space + "UPDATE_SENTENCE_STATUS_TO_HALF_LABELED", params, sqlMapClient);
    }

    /**
     * 根据sid检索已标记的bas_analysis_outsourcing_sentence数据个数
     *
     * @param sid
     * @return
     */
    public Integer selectLabeledSentenceCountWithSid(long sid) {
        Map<String, Object> params = new HashMap<>();
        params.put("sid", sid);
        return (Integer) this.object(space + "SELECT_LABELED_SENTENCE_COUNT_WITH_SID", params, sqlMapClient);
    }

    /**
     * 根据sid检索待校验语句
     *
     * @param sid
     * @return
     */
    public List<String> selectCheckStrListFromOutsourcingSentenceWithSid(long sid) {
        Map<String, Object> params = new HashMap<>();
        params.put("sid", sid);
        return (List<String>) this.list(space + "SELECT_CHECK_STR_LIST_FROM_OUTSOURCING_SENTENCE_WITH_SID", params, sqlMapClient);
    }

    /**
     * 把sid对应的bas_analysis_sentence语句的标记状态(labelStatus)置为已标记(1)
     *
     * @param sid
     */
    public void updateAnalysiSentenceToLabeled(long sid) {
        Map<String, Object> params = new HashMap<>();
        params.put("sid", sid);
        this.update(space + "UPDATE_ANALYSIS_SENTENCE_TO_LABELED", params, sqlMapClient);
    }

    /**
     * 把标记次数小于三的数据的rank值提高为1
     */
    public void updateRankForUnfinishedLabeled() {
        this.update(space + "UPDATE_RANK_FOR_UNFINISHED_LABELED", sqlMapClient);
    }

    /**
     * 把数据需要人工校验的状态加入到表中
     *
     * @param sid
     */
    public void insertOutsourcingSentenceStatus(long sid) {
        Map<String, Object> params = new HashMap<>();
        params.put("sid", sid);
        this.insert(space + "INSERT_OUTSOURCING_SENTENCE_STATUS", params, sqlMapClient);
    }
}
